home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 2 / AACD 2.iso / AACD / Magazine / GraphicsCards / StormMesa / demos / tessdemo.c < prev    next >
C/C++ Source or Header  |  1998-12-15  |  10KB  |  460 lines

  1. /* $Id: tessdemo.c,v 3.3 1998/07/26 01:25:26 brianp Exp $ */
  2.  
  3. /*
  4.  * A demo of the GLU polygon tesselation functions written by Bogdan Sikorski.
  5.  * This demo isn't built by the Makefile because it needs GLUT.  After you've
  6.  * installed GLUT you can try this demo.
  7.  * Here's the command for IRIX, for example:
  8.    cc -g -ansi -prototypes -fullwarn -float -I../include -DSHM tess_demo.c -L../lib -lglut -lMesaGLU -lMesaGL -lm -lX11 -lXext -lXmu -lfpe -lXext -o tess_demo
  9.  */
  10.  
  11.  
  12. /*
  13.  * $Log: tessdemo.c,v $
  14.  * Revision 3.3  1998/07/26 01:25:26  brianp
  15.  * removed include of gl.h and glu.h
  16.  *
  17.  * Revision 3.2  1998/06/29 02:37:30  brianp
  18.  * minor changes for Windows (Ted Jump)
  19.  *
  20.  * Revision 3.1  1998/06/09 01:53:49  brianp
  21.  * main() should return an int
  22.  *
  23.  * Revision 3.0  1998/02/14 18:42:29  brianp
  24.  * initial rev
  25.  *
  26.  */
  27.  
  28.  
  29. #include <GL/glut.h>
  30. #include <stdio.h>
  31. #include <stdlib.h>
  32. #include <string.h>
  33.  
  34. #define MAX_POINTS 200
  35. #define MAX_CONTOURS 50
  36.  
  37. int menu;
  38. typedef enum{ QUIT, TESSELATE, CLEAR } menu_entries;
  39. typedef enum{ DEFINE, TESSELATED } mode_type;
  40. struct
  41. {
  42.     GLint p[MAX_POINTS][2];
  43.     GLuint point_cnt;
  44. } contours[MAX_CONTOURS];
  45. GLuint contour_cnt;
  46. GLsizei width,height;
  47. mode_type mode;
  48.  
  49. struct
  50. {
  51.     GLsizei no;
  52.     GLfloat color[3];
  53.     GLint p[3][2];
  54.     GLclampf p_color[3][3];
  55. } triangle;
  56.  
  57. void CALLBACK my_error(GLenum err)
  58. {
  59.     int len,i;
  60. #ifndef __STORM__
  61.     char const *str;
  62. #else
  63.     const char *str;
  64. #endif
  65.  
  66.     glColor3f(0.9,0.9,0.9);
  67.     glRasterPos2i(5,5);
  68.     str=(const char *)gluErrorString(err);
  69.     len=strlen(str);
  70.     for(i=0;i<len;i++)
  71.         glutBitmapCharacter(GLUT_BITMAP_9_BY_15,str[i]);
  72. }
  73.  
  74. void CALLBACK begin_callback(GLenum mode)
  75. {
  76.     triangle.no=0;
  77. }
  78.  
  79. void CALLBACK edge_callback(GLenum flag)
  80. {
  81.     if(flag==GL_TRUE)
  82.     {
  83.         triangle.color[0]=1.0;
  84.         triangle.color[1]=1.0;
  85.         triangle.color[2]=0.5;
  86.     }
  87.     else
  88.     {
  89.         triangle.color[0]=1.0;
  90.         triangle.color[1]=0.0;
  91.         triangle.color[2]=0.0;
  92.     }
  93. }
  94.  
  95. void CALLBACK end_callback()
  96. {
  97.     glBegin(GL_LINES);
  98.     glColor3f(triangle.p_color[0][0],triangle.p_color[0][1],
  99.         triangle.p_color[0][2]);
  100.     glVertex2i(triangle.p[0][0],triangle.p[0][1]);
  101.     glVertex2i(triangle.p[1][0],triangle.p[1][1]);
  102.     glColor3f(triangle.p_color[1][0],triangle.p_color[1][1],
  103.         triangle.p_color[1][2]);
  104.     glVertex2i(triangle.p[1][0],triangle.p[1][1]);
  105.     glVertex2i(triangle.p[2][0],triangle.p[2][1]);
  106.     glColor3f(triangle.p_color[2][0],triangle.p_color[2][1],
  107.         triangle.p_color[2][2]);
  108.     glVertex2i(triangle.p[2][0],triangle.p[2][1]);
  109.     glVertex2i(triangle.p[0][0],triangle.p[0][1]);
  110.     glEnd();
  111. }
  112.  
  113. void CALLBACK vertex_callback(void *data)
  114. {
  115.     GLsizei no;
  116.     GLint *p;
  117.  
  118.     p=(GLint *)data;
  119.     no=triangle.no;
  120.     triangle.p[no][0]=p[0];
  121.     triangle.p[no][1]=p[1];
  122.     triangle.p_color[no][0]=triangle.color[0];
  123.     triangle.p_color[no][1]=triangle.color[1];
  124.     triangle.p_color[no][2]=triangle.color[2];
  125.     ++(triangle.no);
  126. }
  127.  
  128. void set_screen_wh(GLsizei w, GLsizei h)
  129. {
  130.     width=w;
  131.     height=h;
  132. }
  133.  
  134. #if defined(AMIGA) && defined(__PPC__)
  135. void CALLBACK my_glBegin(GLenum a)
  136. {
  137.     glBegin(a);
  138. }
  139.  
  140. void CALLBACK my_glEnd()
  141. {
  142.     glEnd();
  143. }
  144.  
  145. void CALLBACK my_glVertex2iv(void* a)
  146. {
  147.     glVertex2iv(a);
  148. }
  149.  
  150. #endif
  151.  
  152. void tesse(void)
  153. {
  154.     GLUtriangulatorObj *tobj;
  155.     GLdouble data[3];
  156.     GLuint i,j,point_cnt;
  157.  
  158.     tobj=gluNewTess();
  159.     if(tobj!=NULL)
  160.     {
  161.         glClear(GL_COLOR_BUFFER_BIT);
  162.         glColor3f (0.7, 0.7, 0.0);
  163. #if defined(AMIGA) && defined(__PPC__)
  164.         gluTessCallback(tobj,GLU_BEGIN,(void(CALLBACK *)())my_glBegin);
  165.         gluTessCallback(tobj,GLU_END,(void(CALLBACK *)())my_glEnd);
  166.         gluTessCallback(tobj,GLU_ERROR,(void(CALLBACK *)())my_error);
  167.         gluTessCallback(tobj,GLU_VERTEX,(void(CALLBACK *)())my_glVertex2iv);
  168. #else
  169. #ifndef __STORM__
  170.         gluTessCallback(tobj,GLU_BEGIN,glBegin);
  171.         gluTessCallback(tobj,GLU_END,glEnd);
  172.         gluTessCallback(tobj,GLU_ERROR,my_error);
  173.         gluTessCallback(tobj,GLU_VERTEX,glVertex2iv);
  174. #else
  175.         gluTessCallback(tobj,GLU_BEGIN,(void(CALLBACK *)())glBegin);
  176.         gluTessCallback(tobj,GLU_END,(void(CALLBACK *)())glEnd);
  177.         gluTessCallback(tobj,GLU_ERROR,(void(CALLBACK *)())my_error);
  178.         gluTessCallback(tobj,GLU_VERTEX,(void(CALLBACK *)())glVertex2iv);
  179. #endif
  180. #endif
  181.         gluBeginPolygon(tobj);
  182.         for(j=0;j<=contour_cnt;j++)
  183.         {
  184.             point_cnt=contours[j].point_cnt;
  185.             gluNextContour(tobj,GLU_UNKNOWN);
  186.             for(i=0;i<point_cnt;i++)
  187.             {
  188.                 data[0]=(GLdouble)(contours[j].p[i][0]);
  189.                 data[1]=(GLdouble)(contours[j].p[i][1]);
  190.                 data[2]=0.0;
  191.                 gluTessVertex(tobj,data,contours[j].p[i]);
  192.             }
  193.         }
  194.         gluEndPolygon(tobj);
  195.         glLineWidth(2.0);
  196. #ifndef __STORM__
  197.         gluTessCallback(tobj,GLU_BEGIN,begin_callback);
  198.         gluTessCallback(tobj,GLU_END,end_callback);
  199.         gluTessCallback(tobj,GLU_VERTEX,vertex_callback);
  200.         gluTessCallback(tobj,GLU_EDGE_FLAG,edge_callback);
  201. #else
  202.         gluTessCallback(tobj,GLU_BEGIN,(void(CALLBACK *)())begin_callback);
  203.         gluTessCallback(tobj,GLU_END,(void(CALLBACK *)())end_callback);
  204.         gluTessCallback(tobj,GLU_VERTEX,(void(CALLBACK *)())vertex_callback);
  205.         gluTessCallback(tobj,GLU_EDGE_FLAG,(void(CALLBACK *)())edge_callback);
  206. #endif
  207.         gluBeginPolygon(tobj);
  208.         for(j=0;j<=contour_cnt;j++)
  209.         {
  210.             point_cnt=contours[j].point_cnt;
  211.             gluNextContour(tobj,GLU_UNKNOWN);
  212.             for(i=0;i<point_cnt;i++)
  213.             {
  214.                 data[0]=(GLdouble)(contours[j].p[i][0]);
  215.                 data[1]=(GLdouble)(contours[j].p[i][1]);
  216.                 data[2]=0.0;
  217.                 gluTessVertex(tobj,data,contours[j].p[i]);
  218.             }
  219.         }
  220.         gluEndPolygon(tobj);
  221.         gluDeleteTess(tobj);
  222.         glutMouseFunc(NULL);
  223.         glColor3f (1.0, 1.0, 0.0);
  224.         glLineWidth(1.0);
  225.         mode=TESSELATED;
  226.     }
  227. }
  228.  
  229. void left_down(int x1,int y1)
  230. {
  231.     GLint P[2];
  232.     GLuint point_cnt;
  233.  
  234.     /* translate GLUT into GL coordinates */
  235.     P[0]=x1;
  236.     P[1]=height-y1;
  237.     point_cnt=contours[contour_cnt].point_cnt;
  238.     contours[contour_cnt].p[point_cnt][0]=P[0];
  239.     contours[contour_cnt].p[point_cnt][1]=P[1];
  240.     glBegin(GL_LINES);
  241.     if(point_cnt)
  242.     {
  243.     glVertex2iv(contours[contour_cnt].p[point_cnt-1]);
  244.     glVertex2iv(P);
  245.     }
  246.     else
  247.     {
  248.     glVertex2iv(P);
  249.     glVertex2iv(P);
  250.     }
  251.     glEnd();
  252.     glFinish();
  253.     ++(contours[contour_cnt].point_cnt);
  254. }
  255.  
  256. void middle_down(int x1,int y1)
  257. {
  258.     GLuint point_cnt;
  259.  
  260.     point_cnt=contours[contour_cnt].point_cnt;
  261.     if(point_cnt>2)
  262.     {
  263.         glBegin(GL_LINES);
  264.         glVertex2iv(contours[contour_cnt].p[0]);
  265.         glVertex2iv(contours[contour_cnt].p[point_cnt-1]);
  266.         contours[contour_cnt].p[point_cnt][0]= -1;
  267.         glEnd();
  268.         glFinish();
  269.         contour_cnt++;
  270.         contours[contour_cnt].point_cnt=0;
  271.     }
  272. }
  273.  
  274. void mouse_clicked(int button,int state,int x,int y)
  275. {
  276.     x-= x%10;
  277.     y-= y%10;
  278.     switch(button)
  279.     {
  280.         case GLUT_LEFT_BUTTON:
  281.             if(state==GLUT_DOWN)
  282.                 left_down(x,y);
  283.             break;
  284.         case GLUT_MIDDLE_BUTTON:
  285.             if(state==GLUT_DOWN)
  286.                 middle_down(x,y);
  287.             break;
  288.     }
  289. }
  290.  
  291. void display(void)
  292. {
  293.     GLuint i,j;
  294.     GLuint point_cnt;
  295.  
  296.     glClear(GL_COLOR_BUFFER_BIT);
  297.     switch(mode)
  298.     {
  299.     case DEFINE:
  300.             /* draw grid */
  301.             glColor3f (0.6,0.5,0.5);
  302.             glBegin(GL_LINES);
  303.             for(i=0;i<width;i+=10)
  304.                 for(j=0;j<height;j+=10)
  305.                 {
  306.                     glVertex2i(0,j);
  307.                     glVertex2i(width,j);
  308.                     glVertex2i(i,height);
  309.                     glVertex2i(i,0);
  310.             }
  311.             glColor3f (1.0, 1.0, 0.0);
  312.             for(i=0;i<=contour_cnt;i++)
  313.             {
  314.                 point_cnt=contours[i].point_cnt;
  315.                 glBegin(GL_LINES);
  316.                 switch(point_cnt)
  317.                 {
  318.                     case 0:
  319.                         break;
  320.                     case 1:
  321.                         glVertex2iv(contours[i].p[0]);
  322.                         glVertex2iv(contours[i].p[0]);
  323.                         break;
  324.                     case 2:
  325.                         glVertex2iv(contours[i].p[0]);
  326.                         glVertex2iv(contours[i].p[1]);
  327.                         break;
  328.                     default:
  329.                         --point_cnt;
  330.                         for(j=0;j<point_cnt;j++)
  331.                         {
  332.                             glVertex2iv(contours[i].p[j]);
  333.                             glVertex2iv(contours[i].p[j+1]);
  334.                         }
  335.                         if(contours[i].p[j+1][0]== -1)
  336.                         {
  337.                             glVertex2iv(contours[i].p[0]);
  338.                             glVertex2iv(contours[i].p[j]);
  339.                         }
  340.                         break;
  341.                 }
  342.                 glEnd();
  343.             }
  344.             glFinish();
  345.             break;
  346.         case TESSELATED:
  347.             /* draw lines */
  348.             tesse();
  349.             break;
  350.     }
  351.  
  352.     glColor3f (1.0, 1.0, 0.0);
  353. }
  354.  
  355. void clear( void )
  356. {
  357.     contour_cnt=0;
  358.     contours[0].point_cnt=0;
  359.     glutMouseFunc(mouse_clicked);
  360.     mode=DEFINE;
  361.     display();
  362. }
  363.  
  364. void quit( void )
  365. {
  366.     exit(0);
  367. }
  368.  
  369. void menu_selected(int entry)
  370. {
  371.     switch(entry)
  372.     {
  373.         case CLEAR:
  374.             clear();
  375.             break;
  376.         case TESSELATE:
  377.             tesse();
  378.             break;
  379.         case QUIT:
  380.             quit();
  381.             break;
  382.     }
  383. }
  384.  
  385. void key_pressed(unsigned char key,int x,int y)
  386. {
  387.     switch(key)
  388.     {
  389.         case 't':
  390.         case 'T':
  391.             tesse();
  392.             glFinish();
  393.             break;
  394.         case 'q':
  395.         case 'Q':
  396.             quit();
  397.             break;
  398.         case 'c':
  399.         case 'C':
  400.             clear();
  401.             break;
  402.     }
  403. }
  404.  
  405. void myinit (void) 
  406. {
  407. /*  clear background to gray    */
  408.     glClearColor (0.4, 0.4, 0.4, 0.0);
  409.     glShadeModel (GL_FLAT);    
  410.  
  411.     menu=glutCreateMenu(menu_selected);
  412.     glutAddMenuEntry("clear",CLEAR);
  413.     glutAddMenuEntry("tesselate",TESSELATE);
  414.     glutAddMenuEntry("quit",QUIT);
  415.     glutAttachMenu(GLUT_RIGHT_BUTTON);
  416.     glutMouseFunc(mouse_clicked);
  417.     glutKeyboardFunc(key_pressed);
  418.     contour_cnt=0;
  419.     glPolygonMode(GL_FRONT,GL_FILL);
  420.     mode=DEFINE;
  421. }
  422.  
  423. static void reshape(GLsizei w, GLsizei h)
  424. {
  425.     glViewport(0, 0, w, h);
  426.     glMatrixMode(GL_PROJECTION);
  427.     glLoadIdentity();
  428.     glOrtho(0.0, (GLdouble)w, 0.0, (GLdouble)h, -1.0, 1.0);
  429.     glMatrixMode(GL_MODELVIEW);
  430.     glLoadIdentity();
  431.     set_screen_wh(w,h);
  432. }
  433.  
  434.  
  435. static void usage( void )
  436. {
  437.    printf("Use left mouse button to place vertices.\n");
  438.    printf("Press middle mouse button when done.\n");
  439.    printf("Select tesselate from the pop-up menu.\n");
  440. }
  441.  
  442.  
  443. /*  Main Loop
  444.  *  Open window with initial window size, title bar, 
  445.  *  RGBA display mode, and handle input events.
  446.  */
  447. int main(int argc, char** argv)
  448. {
  449.    usage();
  450.    glutInit(&argc, argv);
  451.    glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB);
  452.    glutInitWindowSize (400, 400);
  453.    glutCreateWindow (argv[0]);
  454.    myinit ();
  455.    glutDisplayFunc(display);
  456.    glutReshapeFunc(reshape);
  457.    glutMainLoop();
  458.    return 0;
  459. }
  460.